//
//  AliPay.m
//  AliPay
//  文档：https://docs.open.alipay.com/204/105295/
//
//  Created by 涂俊 on 2018/1/17.
//  Copyright © 2018年 wyht. All rights reserved.
//

#import "AliPay.h"
#import "OpenSDK_DataKeys.h"
#import "OpenSDK_ReqDataGenerator.h"
#import "OpenSDK_EventManager.h"
#import "OpenSDK_Enum.h"
#import "OpenSDK_EventKeys.h"
#import "OpenSDK_JsonUtil.h"
#import "OpenSDK_StatisticsManager.h"
#import "OpenSDK_PayManager.h"

#import <AlipaySDK/AlipaySDK.h>

@implementation AliPay

{
    NSString *uid;
    //当前的订单信息
    OpenSDK_PayResData *curPayInfo;
}

static NSString *APP_CONFIG=@"AliPayScheme";

#pragma mark - OpenSDK_SdkProtrol声明方法
-(void) initInfo {
    [OpenSDK_EventManager addObsver:self selector:@selector(application_openURL_options:) name:OPENSDK_EVENT_APPLICATION_OPENURL_OPTIONS object:nil className:@"AliPay"];
    [OpenSDK_EventManager addObsver:self selector:@selector(application_openURL_sourceApplication_annotation:) name:OPENSDK_EVENT_APPLICATION_OPENURL_SOURCEAPPLICATION_ANNOTATION object:nil className:@"AliPay"];
}

#pragma mark - OpenSDK_SdkProtrol声明方法 - 服务器唯一标识
-(NSString *) getServerName {
    return @"Alipay";
}

#pragma mark - OpenSDK_PayProtocol声明方法 - 展示的图标
-(NSString *) getDisplayIcon {
    return @"op_pay_ali.png";
}

#pragma mark - OpenSDK_PayProtocol声明方法 - 展示的名字
-(NSString *) getDisplayName {
    return @"支付宝支付";
}

#pragma mark - OpenSDK_PayProtocol声明方法 - 支付平台名
-(NSString *) getPlatform {
    return @"Alipay";
}

#pragma mark - OpenSDK_PayProtocol声明方法 - 支付平台版本号
-(NSString *) getPlatformVersion {
    return @"1.0";
}

#pragma mark - OpenSDK_PayProtocol声明方法 - 统计的类型名
-(NSString *) getStatisticsType {
    return @"ALIPAY";
}

#pragma mark - OpenSDK_PayProtocol声明方法 - 调起第三方平台支付，传入opensdk订单号
-(void) startPay:(OpenSDK_PayResData *) opensdkOrder {
    //订单
    curPayInfo = opensdkOrder;
    //下单uid
    uid = [curPayInfo getUID];
    //服务器端返回的订单加密字符串
    NSDictionary *extra = [opensdkOrder.content objectForKey:@"extra"];
    NSString *orderStr = extra ? [extra objectForKey:@"order_str"] : @"";
    //应用注册scheme,Info.plist定义URL types
    NSString *appScheme = [[[[NSBundle mainBundle] infoDictionary] objectForKey:OpenSDK_CONFIG] objectForKey:APP_CONFIG];
    
    dispatch_async(dispatch_get_main_queue(), ^{
        [[AlipaySDK defaultService] payOrder:orderStr fromScheme:appScheme callback:^(NSDictionary *resultDic) {
            NSLog(@"reslut = %@",resultDic);
            [self processPayResult:resultDic uid:self->uid];
        }];
    });
}


#pragma mark - 支付宝回调需要添加的代码，在系统生命周期回调函数
-(void) application_openURL_sourceApplication_annotation:(NSNotification*) notification {
    if (curPayInfo == nil) {
        return;// 说明该sdk没有调起支付
    }
    NSURL *url = [[notification object] objectForKey:OpenSDK_E_OPENURL];
    if ([url.host isEqualToString:@"safepay"]) {
        // 支付跳转支付宝钱包进行支付，处理支付结果
        [[AlipaySDK defaultService] processOrderWithPaymentResult:url standbyCallback:^(NSDictionary *resultDic) {
            NSLog(@"result = %@",resultDic);
            [self processPayResult:resultDic uid:self->uid];
        }];
    }
}


#pragma mark - 支付宝回调需要添加的代码，在系统生命周期回调函数
// NOTE: 9.0以后使用新API接口
-(void) application_openURL_options:(NSNotification*) notification {
    if (curPayInfo == nil) {
        return;// 说明该sdk没有调起支付
    }
    NSURL *url = [[notification object] objectForKey:OpenSDK_E_OPENURL];
    if ([url.host isEqualToString:@"safepay"]) {
        // 支付跳转支付宝钱包进行支付，处理支付结果
        [[AlipaySDK defaultService] processOrderWithPaymentResult:url standbyCallback:^(NSDictionary *resultDic) {
            NSLog(@"result = %@",resultDic);
            [self processPayResult:resultDic uid:self->uid];
        }];
    }
}


/**
     对于iOS平台而言返回参数是一个NSDictionary对象，对于Android平台而言是一个map结构体。里面有三个key，其中memo是描述信息(类型为字符串)；result是处理结果(类型为json结构字符串)；resultStatus是结果码(类型为字符串)。
     {
     "memo" : "xxxxx",
     "result" : "{
     \"alipay_trade_app_pay_response\":{
     \"code\":\"10000\",
     \"msg\":\"Success\",
     \"app_id\":\"2014072300007148\",
     \"out_trade_no\":\"081622560194853\",
     \"trade_no\":\"2016081621001004400236957647\",
     \"total_amount\":\"0.01\",
     \"seller_id\":\"2088702849871851\",
     \"charset\":\"utf-8\",
     \"timestamp\":\"2016-10-11 17:43:36\"
     },
     \"sign\":\"NGfStJf3i3ooWBuCDIQSumOpaGBcQz+aoAqyGh3W6EqA/gmyPYwLJ2REFijY9XPTApI9YglZyMw+ZMhd3kb0mh4RAXMrb6mekX4Zu8Nf6geOwIa9kLOnw0IMCjxi4abDIfXhxrXyj********\",
     \"sign_type\":\"RSA2\"
     }",
     "resultStatus" : "9000"
     }
 */
-(void) processPayResult:(NSDictionary *)resultDic uid:(NSString *)uid {
    NSString *resultStatus = [resultDic objectForKey:@"resultStatus"];
    if ([@"9000" isEqualToString:resultStatus]) {
        // 9000表示支付成功，去服务器端checkOrder
        NSMutableDictionary *localInfo=[OpenSDK_ReqDataGenerator generateInitDataWithInfo];
        [localInfo setObject:uid forKey:OpenSDK_S_UID];
        [localInfo setObject:[self getPlatform] forKey:OpenSDK_S_PLATFORM];
        [localInfo setObject:[self getPlatformVersion] forKey:OpenSDK_S_PLATFORM_VERSION];
        NSString *localInfoStr=[OpenSDK_ReqDataGenerator generateDataByDictionary:localInfo];
        NSString * resultStr = [resultDic objectForKey:@"result"];
        NSDictionary *resultMap = [OpenSDK_JsonUtil toObjectWithJson:resultStr];
        if (!resultMap) {
            // 统计渠道支付失败
            curPayInfo = nil;
            [[OpenSDK_StatisticsManager getInstance] collectPayFailWithType:OPENSDK_STATS_PAY_SUB_FAIL orderId:nil cpOrderId:[curPayInfo getAppData] detail:[self getStatisticsType] failInfo:@"AliPay Error, Return null"];
            [[OpenSDK_PayManager getInstance] callbackPayFail:@"支付失败,支付宝返回为空" withOrder:nil];
            return;
        }
        
        // 统计渠道支付成功
        [[OpenSDK_StatisticsManager getInstance] collectPaySuccessWithType:OPENSDK_STATS_PAY_SUB_SUCCESS orderId:[curPayInfo getOrderID] cpOrderId:[curPayInfo getAppData] detail:[self getStatisticsType]];
        
        NSDictionary *orderInfoMap = [resultMap objectForKey:@"alipay_trade_app_pay_response"];
        NSString *orderID = [orderInfoMap objectForKey:@"out_trade_no"];// 商户网站唯一订单号
        [self checkOrderWithData:localInfoStr orderID:orderID httpDelegate:^(OpenSDK_BaseResData *resData) {
            if ([resData isOk]) {
                OpenSDK_PayResData *payInfo=[[OpenSDK_PayResData alloc] initWithData:[resData content]];
                if ([[payInfo getPayStatus] isEqualToString:@"SUCCESS"]) {
                    // 统计checkOrder成功
                    [[OpenSDK_StatisticsManager getInstance] collectPaySuccessWithType:OPENSDK_STATS_PAY_SUB_CHECK_SUCCESS orderId:[self->curPayInfo getOrderID] cpOrderId:[self->curPayInfo getAppData] detail:[self getStatisticsType]];
                    // 回调外部支付成功
                    self->curPayInfo = nil;
                    OpenSDK_OrderInfo *userOrderInfo=[payInfo toUserOrderInfo];
                    [[OpenSDK_PayManager getInstance] callbackPaySuccess:nil withOrder:userOrderInfo];
                } else if ([[payInfo getPayStatus] isEqualToString:@"FAIL"]) {
                    // 统计checkOrder失败
                    [[OpenSDK_StatisticsManager getInstance] collectPayFailWithType:OPENSDK_STATS_PAY_SUB_CHECK_FAIL orderId:nil cpOrderId:[self->curPayInfo getAppData] detail:[self getStatisticsType] failInfo:@"Order status is FAIL"];
                    // 回调外部支付失败
                    self->curPayInfo = nil;
                    [[OpenSDK_PayManager getInstance] callbackPayFail:@"订单支付失败" withOrder:nil];
                } else {
                    // 统计checkOrder为PAY_WAIT_CHECK状态
                    [[OpenSDK_StatisticsManager getInstance] collectPayFailWithType:OPENSDK_STATS_PAY_SUB_CHECK_FAIL orderId:nil cpOrderId:[self->curPayInfo getAppData] detail:[self getStatisticsType] failInfo:@"Order status is NEW"];
                    // CheckOrder是NeW状态，则回调外部OpenSDK_PAY_WAIT_CHECK
                    self->curPayInfo = nil;
                    OpenSDK_OrderInfo *userOrderInfo=[payInfo toUserOrderInfo];
                    [[OpenSDK_PayManager getInstance] callbackPayWaitCheck:userOrderInfo];
                }
            } else {
                // 统计checkOrder网络失败
                [[OpenSDK_StatisticsManager getInstance] collectPayFailWithType:OPENSDK_STATS_PAY_SUB_CHECK_FAIL orderId:nil cpOrderId:[self->curPayInfo getAppData] detail:[self getStatisticsType] failInfo:[resData errorMsg]];
                // 回调外部
                self->curPayInfo = nil;
                [[OpenSDK_PayManager getInstance] callbackPayFail:[resData errorMsg] withOrder:nil];
            }
            NSLog(@"++++++++++++++++++++++++++++++订单处理结束");
        }];
    } else {
        // 统计渠道支付失败
        [[OpenSDK_StatisticsManager getInstance] collectPayFailWithType:OPENSDK_STATS_PAY_SUB_FAIL orderId:nil cpOrderId:[curPayInfo getAppData] detail:[self getStatisticsType] failInfo:[@"AliPay Error," stringByAppendingString:[resultDic objectForKey:@"memo"]]];
        curPayInfo = nil;
        [[OpenSDK_PayManager getInstance] callbackPayFail:[@"支付失败," stringByAppendingString:[resultDic objectForKey:@"memo"]] withOrder:nil];
    }
}

@end
